import { _decorator, Component, Node, Mat4, Vec3, Quat, Camera, Vec2, CCBoolean } from 'cc';
import { InputManager } from '../input/input_manager';
const { ccclass, property } = _decorator;

let _tempVec3: Vec3 = new Vec3;
let _matView: Mat4 = new Mat4;

@ccclass('RoamCamera')
export class RoamCamera extends Component {
    @property({ tooltip: '启用默认输入' })
    resetDefaultControl: boolean = false;

    @property({ tooltip: '旋转速度' })
    rotateSpeed = 30;

    @property({ tooltip: '移动速度' })
    moveSpeed = 7;

    private _camera: Camera | null = null;

    private _forwardVector: Vec3 = new Vec3;     // 摄像机向前的向量
    private _rightVector: Vec3 = new Vec3;       // 摄像机向右的向量
    private _upVector: Vec3 = new Vec3;          // 摄像机向上的向量

    private _primary: Vec2 | null = null;
    private _secondary: Vec2 | null = null;
    private _scroll: Vec2 | null = null;

    start () {
        this._camera = this.node.getComponent(Camera);

        if (this.resetDefaultControl) {
            this.bindInput(InputManager.instance.primaryMovement, InputManager.instance.secondaryMovement, InputManager.instance.scroll)
        }
    }

    /**
     * 绑定输入
     * @param primary 
     * @param secondary 
     * @param scroll 
     */
    public bindInput (primary: Vec2 | null, secondary: Vec2 | null, scroll: Vec2 | null) {
        this._primary = primary;
        this._secondary = secondary;
        this._scroll = scroll;
    }

    update (deltaTime: number) {
        if (this._camera) {
            Mat4.invert(_matView, this._camera.node.worldMatrix);

            this._rightVector.x = _matView.m00;
            this._rightVector.y = _matView.m04;
            this._rightVector.z = _matView.m08;

            this._upVector.x = _matView.m01;
            this._upVector.y = _matView.m05;
            this._upVector.z = _matView.m09;

            this._forwardVector.x = -_matView.m02;
            this._forwardVector.y = -_matView.m06;
            this._forwardVector.z = -_matView.m10;

            if (this._primary && this._primary.length() > 0) {
                this._camera.node.getPosition(_tempVec3);
                Vec3.scaleAndAdd(_tempVec3, _tempVec3, this._forwardVector, deltaTime * this._primary.y * this.moveSpeed);
                Vec3.scaleAndAdd(_tempVec3, _tempVec3, this._rightVector, deltaTime * this._primary.x * this.moveSpeed);
                this._camera.node.setPosition(_tempVec3);
            }

            if (this._secondary && this._secondary.length() > 0) {
                Vec3.copy(_tempVec3, this._camera.node.eulerAngles);
                _tempVec3.y -= this._secondary.x * deltaTime * this.rotateSpeed;
                _tempVec3.x += this._secondary.y * deltaTime * this.rotateSpeed;
                this._camera.node!.setRotationFromEuler(_tempVec3);
            }
        }
    }
}

